home *** CD-ROM | disk | FTP | other *** search
/ SGI Freeware 2002 November / SGI Freeware 2002 November - Disc 3.iso / dist / fw_qt3.idb / usr / freeware / Qt / examples / opengl / gear / gear.cpp.z / gear.cpp
C/C++ Source or Header  |  2002-04-08  |  8KB  |  298 lines

  1. /****************************************************************************
  2. ** $Id:  qt/gear.cpp   3.0.3   edited Oct 12 12:18 $
  3. **
  4. ** Copyright (C) 1992-2000 Trolltech AS.  All rights reserved.
  5. **
  6. ** This file is part of an example program for Qt.  This example
  7. ** program may be used, distributed and modified without limitation.
  8. **
  9. *****************************************************************************/
  10. //
  11. // Draws a gear.
  12. //
  13. // Portions of this code have been borrowed from Brian Paul's Mesa
  14. // distribution.
  15. //
  16.  
  17. #include <qgl.h>
  18. #include <qapplication.h>
  19. #include <math.h>
  20.  
  21. #if defined(Q_CC_MSVC)
  22. #pragma warning(disable:4305) // init: truncation from const double to float
  23. #endif
  24.  
  25. /*
  26.  * Draw a gear wheel.  You'll probably want to call this function when
  27.  * building a display list since we do a lot of trig here.
  28.  *
  29.  * Input:  inner_radius - radius of hole at center
  30.  *       outer_radius - radius at center of teeth
  31.  *       width - width of gear
  32.  *       teeth - number of teeth
  33.  *       tooth_depth - depth of tooth
  34.  */
  35. static void gear( GLfloat inner_radius, GLfloat outer_radius, GLfloat width,
  36.           GLint teeth, GLfloat tooth_depth )
  37. {
  38.     GLint i;
  39.     GLfloat r0, r1, r2;
  40.     GLfloat angle, da;
  41.     GLfloat u, v, len;
  42.  
  43.     r0 = inner_radius;
  44.     r1 = outer_radius - tooth_depth/2.0;
  45.     r2 = outer_radius + tooth_depth/2.0;
  46.  
  47.     const double pi = 3.14159264;
  48.     da = 2.0*pi / teeth / 4.0;
  49.  
  50.     glShadeModel( GL_FLAT );
  51.  
  52.     glNormal3f( 0.0, 0.0, 1.0 );
  53.  
  54.     /* draw front face */
  55.     glBegin( GL_QUAD_STRIP );
  56.     for (i=0;i<=teeth;i++) {
  57.     angle = i * 2.0*pi / teeth;
  58.     glVertex3f( r0*cos(angle), r0*sin(angle), width*0.5 );
  59.     glVertex3f( r1*cos(angle), r1*sin(angle), width*0.5 );
  60.     glVertex3f( r0*cos(angle), r0*sin(angle), width*0.5 );
  61.     glVertex3f( r1*cos(angle+3*da), r1*sin(angle+3*da), width*0.5 );
  62.     }
  63.     glEnd();
  64.  
  65.     /* draw front sides of teeth */
  66.     glBegin( GL_QUADS );
  67.     da = 2.0*pi / teeth / 4.0;
  68.     for (i=0;i<teeth;i++) {
  69.     angle = i * 2.0*pi / teeth;
  70.  
  71.     glVertex3f( r1*cos(angle),      r1*sin(angle),      width*0.5 );
  72.     glVertex3f( r2*cos(angle+da),   r2*sin(angle+da),      width*0.5 );
  73.     glVertex3f( r2*cos(angle+2*da), r2*sin(angle+2*da), width*0.5 );
  74.     glVertex3f( r1*cos(angle+3*da), r1*sin(angle+3*da), width*0.5 );
  75.     }
  76.     glEnd();
  77.  
  78.  
  79.     glNormal3f( 0.0, 0.0, -1.0 );
  80.  
  81.     /* draw back face */
  82.     glBegin( GL_QUAD_STRIP );
  83.     for (i=0;i<=teeth;i++) {
  84.     angle = i * 2.0*pi / teeth;
  85.     glVertex3f( r1*cos(angle), r1*sin(angle), -width*0.5 );
  86.     glVertex3f( r0*cos(angle), r0*sin(angle), -width*0.5 );
  87.     glVertex3f( r1*cos(angle+3*da), r1*sin(angle+3*da), -width*0.5 );
  88.     glVertex3f( r0*cos(angle), r0*sin(angle), -width*0.5 );
  89.     }
  90.     glEnd();
  91.  
  92.     /* draw back sides of teeth */
  93.     glBegin( GL_QUADS );
  94.     da = 2.0*pi / teeth / 4.0;
  95.     for (i=0;i<teeth;i++) {
  96.     angle = i * 2.0*pi / teeth;
  97.  
  98.     glVertex3f( r1*cos(angle+3*da), r1*sin(angle+3*da), -width*0.5 );
  99.     glVertex3f( r2*cos(angle+2*da), r2*sin(angle+2*da), -width*0.5 );
  100.     glVertex3f( r2*cos(angle+da),   r2*sin(angle+da),      -width*0.5 );
  101.     glVertex3f( r1*cos(angle),      r1*sin(angle),      -width*0.5 );
  102.     }
  103.     glEnd();
  104.  
  105.  
  106.     /* draw outward faces of teeth */
  107.     glBegin( GL_QUAD_STRIP );
  108.     for (i=0;i<teeth;i++) {
  109.     angle = i * 2.0*pi / teeth;
  110.  
  111.     glVertex3f( r1*cos(angle),      r1*sin(angle),       width*0.5 );
  112.     glVertex3f( r1*cos(angle),      r1*sin(angle),      -width*0.5 );
  113.     u = r2*cos(angle+da) - r1*cos(angle);
  114.     v = r2*sin(angle+da) - r1*sin(angle);
  115.     len = sqrt( u*u + v*v );
  116.     u /= len;
  117.     v /= len;
  118.     glNormal3f( v, -u, 0.0 );
  119.     glVertex3f( r2*cos(angle+da),   r2*sin(angle+da),       width*0.5 );
  120.     glVertex3f( r2*cos(angle+da),   r2*sin(angle+da),      -width*0.5 );
  121.     glNormal3f( cos(angle), sin(angle), 0.0 );
  122.     glVertex3f( r2*cos(angle+2*da), r2*sin(angle+2*da),  width*0.5 );
  123.     glVertex3f( r2*cos(angle+2*da), r2*sin(angle+2*da), -width*0.5 );
  124.     u = r1*cos(angle+3*da) - r2*cos(angle+2*da);
  125.     v = r1*sin(angle+3*da) - r2*sin(angle+2*da);
  126.     glNormal3f( v, -u, 0.0 );
  127.     glVertex3f( r1*cos(angle+3*da), r1*sin(angle+3*da),  width*0.5 );
  128.     glVertex3f( r1*cos(angle+3*da), r1*sin(angle+3*da), -width*0.5 );
  129.     glNormal3f( cos(angle), sin(angle), 0.0 );
  130.     }
  131.  
  132.     glVertex3f( r1*cos(0.0), r1*sin(0.0), width*0.5 );
  133.     glVertex3f( r1*cos(0.0), r1*sin(0.0), -width*0.5 );
  134.  
  135.     glEnd();
  136.  
  137.  
  138.     glShadeModel( GL_SMOOTH );
  139.  
  140.     /* draw inside radius cylinder */
  141.     glBegin( GL_QUAD_STRIP );
  142.     for (i=0;i<=teeth;i++) {
  143.     angle = i * 2.0*pi / teeth;
  144.     glNormal3f( -cos(angle), -sin(angle), 0.0 );
  145.     glVertex3f( r0*cos(angle), r0*sin(angle), -width*0.5 );
  146.     glVertex3f( r0*cos(angle), r0*sin(angle), width*0.5 );
  147.     }
  148.     glEnd();
  149.  
  150. }
  151.  
  152.  
  153. static GLfloat view_rotx=20.0, view_roty=30.0, view_rotz=0.0;
  154. static GLint gear1, gear2, gear3;
  155. static GLfloat angle = 0.0;
  156.  
  157.  
  158. static void draw()
  159. {
  160.     angle += 2.0;
  161.     view_roty += 1.0;
  162.  
  163.     glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT );
  164.  
  165.     glPushMatrix();
  166.     glRotatef( view_rotx, 1.0, 0.0, 0.0 );
  167.     glRotatef( view_roty, 0.0, 1.0, 0.0 );
  168.     glRotatef( view_rotz, 0.0, 0.0, 1.0 );
  169.  
  170.     glPushMatrix();
  171.     glTranslatef( -3.0, -2.0, 0.0 );
  172.     glRotatef( angle, 0.0, 0.0, 1.0 );
  173.     glCallList(gear1);
  174.     glPopMatrix();
  175.  
  176.     glPushMatrix();
  177.     glTranslatef( 3.1, -2.0, 0.0 );
  178.     glRotatef( -2.0*angle-9.0, 0.0, 0.0, 1.0 );
  179.     glCallList(gear2);
  180.     glPopMatrix();
  181.  
  182.     glPushMatrix();
  183.     glTranslatef( -3.1, 2.2, -1.8 );
  184.     glRotatef( 90.0, 1.0, 0.0, 0.0 );
  185.     glRotatef( 2.0*angle-2.0, 0.0, 0.0, 1.0 );
  186.     glCallList(gear3);
  187.     glPopMatrix();
  188.  
  189.     glPopMatrix();
  190. }
  191.  
  192.  
  193. static int timer_interval = 10;            // timer interval (millisec)
  194.  
  195.  
  196. class GearWidget : public QGLWidget
  197. {
  198. public:
  199.     GearWidget( QWidget *parent=0, const char *name=0 );
  200. protected:
  201.     void initializeGL();
  202.     void resizeGL( int, int );
  203.     void paintGL();
  204.     void timerEvent( QTimerEvent * );
  205. };
  206.  
  207. GearWidget::GearWidget( QWidget *parent, const char *name )
  208.      : QGLWidget( parent, name )
  209. {
  210.     startTimer( timer_interval );
  211. }
  212.  
  213. void GearWidget::initializeGL()
  214. {
  215.     static GLfloat pos[4] = {5.0, 5.0, 10.0, 1.0 };
  216.     static GLfloat ared[4] = {0.8, 0.1, 0.0, 1.0 };
  217.     static GLfloat agreen[4] = {0.0, 0.8, 0.2, 1.0 };
  218.     static GLfloat ablue[4] = {0.2, 0.2, 1.0, 1.0 };
  219.  
  220.     glLightfv( GL_LIGHT0, GL_POSITION, pos );
  221.     glEnable( GL_CULL_FACE );
  222.     glEnable( GL_LIGHTING );
  223.     glEnable( GL_LIGHT0 );
  224.     glEnable( GL_DEPTH_TEST );
  225.  
  226.     /* make the gears */
  227.     gear1 = glGenLists(1);
  228.     glNewList(gear1, GL_COMPILE);
  229.     glMaterialfv( GL_FRONT, GL_AMBIENT_AND_DIFFUSE, ared );
  230.     gear( 1.0, 4.0, 1.0, 20, 0.7 );
  231.     glEndList();
  232.  
  233.     gear2 = glGenLists(1);
  234.     glNewList(gear2, GL_COMPILE);
  235.     glMaterialfv( GL_FRONT, GL_AMBIENT_AND_DIFFUSE, agreen );
  236.     gear( 0.5, 2.0, 2.0, 10, 0.7 );
  237.     glEndList();
  238.  
  239.     gear3 = glGenLists(1);
  240.     glNewList(gear3, GL_COMPILE);
  241.     glMaterialfv( GL_FRONT, GL_AMBIENT_AND_DIFFUSE, ablue );
  242.     gear( 1.3, 2.0, 0.5, 10, 0.7 );
  243.     glEndList();
  244.  
  245.     glEnable( GL_NORMALIZE );
  246. }
  247.  
  248.  
  249. void GearWidget::resizeGL( int width, int height )
  250. {
  251.     GLfloat w = (float) width / (float) height;
  252.     GLfloat h = 1.0;
  253.  
  254.     glViewport( 0, 0, width, height );
  255.     glMatrixMode(GL_PROJECTION);
  256.     glLoadIdentity();
  257.     glFrustum( -w, w, -h, h, 5.0, 60.0 );
  258.     glMatrixMode(GL_MODELVIEW);
  259.     glLoadIdentity();
  260.     glTranslatef( 0.0, 0.0, -40.0 );
  261. }
  262.  
  263.  
  264. void GearWidget::paintGL()
  265. {
  266.     draw();
  267. }
  268.  
  269. void GearWidget::timerEvent(QTimerEvent*)
  270. {
  271.     updateGL();
  272. }
  273.  
  274.  
  275.  
  276. int main( int argc, char **argv )
  277. {
  278.     QApplication::setColorSpec( QApplication::CustomColor );
  279.     QApplication a( argc, argv );
  280.  
  281.     if ( !QGLFormat::hasOpenGL() ) {
  282.     qWarning( "This system has no OpenGL support. Exiting." );
  283.     return -1;
  284.     }
  285.  
  286.     if ( argc >= 2 ) {
  287.     bool ok = TRUE;
  288.     timer_interval = QString::fromLatin1( argv[1] ).toInt( &ok );
  289.     if ( !ok )
  290.         timer_interval = 10;
  291.     }
  292.  
  293.     GearWidget w;
  294.     a.setMainWidget( &w );
  295.     w.show();
  296.     return a.exec();
  297. }
  298.